#! /usr/bin/env perl

###########################################################################
#
# vcommit
#
###########################################################################
#
# This command commits changes to the repository.  It is a fairly thin wrapper around the VC's checkin or commit
# command, although it provides some extra functionality as well.
#
# #########################################################################
#
# All the code herein is released under the Artistic License
#		( http://www.perl.com/language/misc/Artistic.html )
# Copyright (c) 2000-2010 Barefoot Software, Copyright (c) 2004-2007 ThinkGeek
#
###########################################################################

use strict;
use warnings;

use VCtools::Base;
use VCtools::Args;
use VCtools::Common;


#################################
# OPTIONS AND ARGUMENTS
#################################

VCtools::switch('recursive', 'r', 'operate recursively');
VCtools::switch('fix_log', 'f', 're-edit the last commit log for the file(s) to fix some mistake');
VCtools::switch('message', 'm', 'specify commit message instead of using editor (does not work with -f)', 'commit_message');
VCtools::args('files', 'list', 'file(s) (or directory/ies) to commit');
VCtools::getopts();

# remember, directories are files too
my @files = VCtools::files();


#################################
# CHECK FOR ERRORS
#################################

my $proj = VCtools::verify_files_and_group(@files);

# get statuses for everything at once (quicker that way)
VCtools::cache_file_status(@files);

# if we're doing recursive, we really need the list of
# modified files for each directory in our list
# so do that here
if (VCtools::recursive())
{
	my @orig_files = @files;
	@files = ();

	foreach my $file (@orig_files)
	{
		if (-d $file)
		{
			$file .= '/' unless substr($file, -1) eq '/';
			my @subdir_files = VCtools::get_all_with_status('modified', $file);
			print STDERR "recursive file searching yields @subdir_files\n" if DEBUG >= 3;
			push @files, @subdir_files;
		}
		else
		{
			push @files, $file;
		}
	}
}

# right here, think of a way to do similar for lockers

my @files_to_add;
foreach my $file (@files)
{
	unless (VCtools::exists_in_vc($file))
	{
		# -f requires file must exist in VC
		if (not VCtools::fix_log() and VCtools::yesno("$file does not exist in VC; add it?"))
		{
			push @files_to_add, $file;
		}
		else
		{
			VCtools::fatal_error("$file is not in VC");
		}
	}

	# for -f, we don't have to have modifications
	# (in fact, generally we won't)
	unless (VCtools::fix_log())
	{
=not_working_with_svn_yet
		VCtools::fatal_error("you didn't vget on $file") unless VCtools::user_is_a_locker($file);

		if (@lockers > 1)
		{
			# user must be in the list, else would have err'ed out above
			# but more than one name is in the list, so ...
			print STDERR "$me: other people are currently editing this file!\n";
			print STDERR "     $file is currently being edited by: @lockers\n";
			if (not yesno("Do you want to proceed anyway?"))
			{
				exit 1;
			}
		}
=cut

		print STDERR "outdated is ", VCtools::outdated_by_vc($file),
				", modified is ", VCtools::modified_from_vc($file), "\n" if DEBUG >= 2;
		VCtools::fatal_error("file $file is outdated (vsync to merge your revisions with the latest repository changes)")
				if VCtools::outdated_by_vc($file);
		VCtools::fatal_error("file $file has no changes to commit (vunget to remove your editing status)")
				unless VCtools::modified_from_vc($file);
	}
}

# for CVS, at a minimum, would need to check for sticky tags here
# not sure what to in a generic fashion


#################################
# MAIN
#################################

if (VCtools::fix_log())
{
	# use of HEAD here is a Subversion-specific cheat
	VCtools::edit_commit_log($_, 'HEAD') foreach @files;
}
else
{
	VCtools::add_files(@files_to_add, { DONT_RECURSE => 1 } ) if @files_to_add;
	VCtools::commit_files($proj, @files, { MESSAGE => VCtools::message() } );
=not_working_with_svn_yet
	VCtools::release_edit_flag(@files);
=cut
}

print "done\n";


#################################
# SUBS
#################################
